﻿using Autodesk.Revit.Attributes;
using Autodesk.Revit.DB.ExtensibleStorage;
using Autodesk.Revit.DB;
using Autodesk.Revit.UI;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.IO;
using System.Windows;
using System.Windows.Documents;
using System.Windows.Input;

namespace ZhuXingFamilys.ExportExcel.utils
{
    public class StoreElement : IExternalEventHandler
    {
        public string key { set; get; } // 保存的key
        public IList<string> saveList { set; get; } // 保存的数据
        public string scheduleName { set; get; } // 保存的名称
        public string dataStorageName { set; get; } // 存储器名称
        public string guid { set; get; } // 删除的GUID
        public int type { set; get; } // 操作逻辑 0:保存；1:删除

        public void Execute(UIApplication uiapp)
        {
			UIDocument activeUIDoc = uiapp.ActiveUIDocument;
            Document doc = activeUIDoc.Document;
            if(type == 0)
            {
                using (var trans = new Transaction(doc, "SaveSchemaListForZhuXing"))
                {
                    try
                    {
                        trans.Start();
                        // 查询是否存在DataStorage
                        FilteredElementCollector collector = new FilteredElementCollector(doc);
                        var dataStorageList = collector.OfClass(typeof(DataStorage)).ToList();
                        DataStorage myDataStorage;
                        // 不存在则创建
                        if (dataStorageList == null || dataStorageList.Count == 0)
                        {
                            //创建数据存储对象
                            myDataStorage = DataStorage.Create(doc);
                            //这里使用Name作为筛选dataStorage的条件，要注意命名的唯一性
                            myDataStorage.Name = dataStorageName;
                        }
                        // 存在则直接使用
                        else
                        {
                            myDataStorage = dataStorageList.FirstOrDefault(o => o.Name == dataStorageName) as DataStorage;
                            if (myDataStorage == null)
                            {
                                //创建数据存储对象
                                myDataStorage = DataStorage.Create(doc);
                                //这里使用Name作为筛选dataStorage的条件，要注意命名的唯一性
                                myDataStorage.Name = dataStorageName;
                            }
                        }

                        IList<Guid> schemaGuids = myDataStorage.GetEntitySchemaGuids();
                        Schema targetSchema = null;
                        // 判断是否存在重名schema
                        foreach (var schemaGuid in schemaGuids)
                        {
                            Schema schema = Schema.Lookup(schemaGuid);
                            if (schema.SchemaName == scheduleName)
                            {
                                targetSchema = schema;
                                break;
                            }
                        }
                        // 不存在重名
                        if(targetSchema == null )
                        {
                            //创建框架构造器
                            SchemaBuilder builder = new SchemaBuilder(Guid.NewGuid());
                            builder.SetReadAccessLevel(AccessLevel.Public);
                            builder.SetWriteAccessLevel(AccessLevel.Public);
                            builder.SetSchemaName(scheduleName);
                            //注意存储数组的时候，FieldType不能给数组类型，而要给元素类型
                            //如果元素类型是一个集合，需要给接口类型，例如IList<T>
                            builder.AddArrayField(key, typeof(string));
                            //注册schema
                            targetSchema = builder.Finish();
                            //创建schema实例entity
                            var entity = new Entity(targetSchema);
                            //获取属性
                            var field = targetSchema.GetField(key);
                            //为属性赋值
                            //为数组属性赋值的时候，不能使用数组，而是使用IList<T>,因为Revit无法识别数组类型
                            entity.Set<IList<string>>(field, saveList);
                            //将schema添加到数据储存对象中
                            myDataStorage.SetEntity(entity);
                            //更新模型
                            doc.Regenerate();
                            trans.Commit();
							ExportToExcel exporttoexcel = ExportToExcel.GetInstance();
							exporttoexcel.loadExcelWindows();
							MessageBox.Show("保存成功", "提示");
                        }
                        // 存在重名
                        else
                        {
                            MessageBoxResult result = MessageBox.Show("项目中已存在名称为'" + scheduleName + "'的工程量清单表，是否替换？", "提示", MessageBoxButton.YesNo);
                            if (result == MessageBoxResult.Yes)
                            {
                                //删除
                                myDataStorage.DeleteEntity(targetSchema);
                                //创建框架构造器
                                SchemaBuilder builder = new SchemaBuilder(Guid.NewGuid());
                                builder.SetReadAccessLevel(AccessLevel.Public);
                                builder.SetWriteAccessLevel(AccessLevel.Public);
                                builder.SetSchemaName(scheduleName);
                                //注意存储数组的时候，FieldType不能给数组类型，而要给元素类型
                                //如果元素类型是一个集合，需要给接口类型，例如IList<T>
                                builder.AddArrayField(key, typeof(string));
                                //注册schema
                                targetSchema = builder.Finish();
                                //创建schema实例entity
                                var entity = new Entity(targetSchema);
                                //获取属性
                                var field = targetSchema.GetField(key);
                                //为属性赋值
                                //为数组属性赋值的时候，不能使用数组，而是使用IList<T>,因为Revit无法识别数组类型
                                entity.Set<IList<string>>(field, saveList);
                                //将schema添加到数据储存对象中
                                myDataStorage.SetEntity(entity);
                                //更新模型
                                doc.Regenerate();
                                trans.Commit();
								ExportToExcel exporttoexcel = ExportToExcel.GetInstance();
                                exporttoexcel.loadExcelWindows();
								MessageBox.Show("保存成功", "提示");
							}
                        }
                    }
                    catch (Exception e)
                    {
                        if (e.Message.Contains("The parameter schemaName is not acceptable for naming Extensible Storage objects."))
                        {
                            MessageBox.Show("因Revit限制，名称不能以数字开头且不能包含'-','*'等特殊符号，请修改后重新保存");
                        }
                        else
                        {
                            MessageBox.Show("保存失败；/n原因：" + e.Message);
                        }
                    }
                }
            }
            else if (type == 1)
            {
                using (var trans = new Transaction(doc, "DeleteSchemaListForZhuXing"))
                {
                    try
                    {
                        trans.Start();
                        // 查询是否存在DataStorage
                        FilteredElementCollector collector = new FilteredElementCollector(doc);
                        var dataStorageList = collector.OfClass(typeof(DataStorage)).ToList();
                        DataStorage myDataStorage = dataStorageList.FirstOrDefault(o => o.Name == dataStorageName) as DataStorage;

                        IList<Guid> schemaGuids = myDataStorage.GetEntitySchemaGuids();

                        Schema targetSchema = null;
                        foreach (var schemaGuid in schemaGuids)
                        {
                            Schema schema = Schema.Lookup(schemaGuid);
                            if (schema.SchemaName == scheduleName)
                            {
                                targetSchema = schema;
                                break;
                            }
                        }
                        if(targetSchema!=null) 
                        {
                            myDataStorage.DeleteEntity(targetSchema);
						}
						//更新模型
						doc.Regenerate();
                        trans.Commit();
                        //MessageBox.Show("删除成功", "提示");
                    }
                    catch (Exception e)
                    {
                        if (e.Message.Contains("The parameter schemaName is not acceptable for naming Extensible Storage objects."))
                        {
                            MessageBox.Show("因Revit限制，保存的工程名称不能以数字开头，请修改后重新保存");
                        }
                        else
                        {
                            MessageBox.Show("删除失败；/n原因：" + e.Message);
                        }
                    }
                }
            }
            
        }
        public string GetName()
        {
            return "StoreElement";
        }
        
    }
}
